﻿using System;
using System.Collections.Generic;
using System.Configuration.Abstractions;
using SimpleInjector;
using Sustainalytics.Entities;
using Sustainalytics.Entities.Governance;
using Sustainalytics.Synchronization.Interface;
using Sustainalytics.MongoDB.Extensions;
using Sustainalytics.ClientDW.Entities;
using Sustainalytics.BusinessResearchProductStates.Entities.ResearchState;

namespace Sustainalytics.Governance.Computing
{
    public static class SimpleInjectorConfig
    {
        public static Dictionary<string, string> ConnectionStrings { get; set; }

        public static Container Register(ILogger logger, Dictionary<string, string> gaConnectionStrings)
        {
            var container = new Container();

            if (gaConnectionStrings == null || gaConnectionStrings.Count == 0)
                throw new ArgumentException("Connection strings must be provided in order to register!");


            container.RegisterCollections(gaConnectionStrings);

            container.RegisterMisc(logger);

            container.Register<GovernanceDataManager>();
            container.Register<GovernanceComputationEngine>();

            container.Verify();

            return container;
        }


        private static void RegisterCollections(this Container container, Dictionary<string, string> gaConnectionStrings)
        {
            if (!gaConnectionStrings.TryGetValue("ClientDW", out string clientDwConnectionString))
            {
                throw new ArgumentException("No connection string found for ClientDW!");
            }

            if (!gaConnectionStrings.TryGetValue("GovernanceDW", out string governanceDwConnectionString))
            {
                throw new ArgumentException("No connection string found for GovernanceDW!");
            }
            
            container.Register(() => MongoFactory.GetCollectionFromDatabase<GovernanceCompanyProfile>(governanceDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<GovernanceIndicatorTemplate>(governanceDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<GovernanceIndicator>(governanceDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<GovernanceComputationResult>(governanceDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<GovernanceAssessmentThreshold>(governanceDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<CorporateData>(clientDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<CompanyProfileResearchState>(clientDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<GovernanceIssue>(governanceDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<GovernanceSource>(governanceDwConnectionString));
            container.Register(() => MongoFactory.GetCollectionFromDatabase<SharedEntities.CorporateGovernanceResearch.CorporateGovernanceResearchProfile>(governanceDwConnectionString));
        }

        private static void RegisterMisc(this Container container, ILogger logger)
        {
            container.Register(() => logger, Lifestyle.Singleton);
            container.RegisterSingleton(() => ConfigurationManager.Instance.AppSettings);
        }
    }
}
